package com.zmc.lostfound.post.service.impl;

import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.collection.CollectionUtil;
import cn.hutool.core.util.StrUtil;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.zmc.lostfound.common.exception.MyException;
import com.zmc.lostfound.common.utils.PageParams;
import com.zmc.lostfound.common.utils.PageResult;
import com.zmc.lostfound.common.utils.Result;
import com.zmc.lostfound.common.utils.redis.RedisCacheUtil;
import com.zmc.lostfound.post.dao.ItemTypeDao;
import com.zmc.lostfound.post.entity.ItemTypeEntity;
import com.zmc.lostfound.post.service.ItemTypeService;
import com.zmc.lostfound.post.vo.ItemTypeSaveVO;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.List;
import java.util.concurrent.TimeUnit;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import java.util.stream.Collectors;

import static com.zmc.lostfound.common.constant.RedisConstant.CACHE_ITEM_TYPE_LIST_KEY;
import static com.zmc.lostfound.common.constant.RedisConstant.CACHE_ITEM_TYPE_LIST_KEY_TTL;

/**
 * @author LJQ
 * @description 物品类型管理业务实现类
 */
@Service
public class ItemTypeServiceImpl extends ServiceImpl<ItemTypeDao, ItemTypeEntity> implements ItemTypeService {

    private final RedisCacheUtil redisCacheUtil;

    public ItemTypeServiceImpl(RedisCacheUtil redisCacheUtil) {
        this.redisCacheUtil = redisCacheUtil;
    }

    /**
     * 分页模糊查询物品类型
     *
     * @param pageParams 分页参数
     * @return PageResult
     */
    @Override
    public PageResult queryPage(PageParams pageParams) {
        Integer pageNo = pageParams.getPageNo();
        Integer pageSize = pageParams.getPageSize();
        String keyword = pageParams.getKeyword();
        PageResult pageResult = new PageResult(pageNo, pageSize);
        // 1.查询所有物品类型
        List<ItemTypeEntity> itemTypeList = this.findAll();
        // 2.大小写不敏感的模糊查询
        if (StrUtil.isNotBlank(keyword)) {
            Pattern pattern = Pattern.compile(keyword, Pattern.CASE_INSENSITIVE);
            itemTypeList = itemTypeList.stream()
                    .filter(itemTypeEntity -> {
                        Matcher matcher = pattern.matcher((itemTypeEntity.getType()));
                        return (matcher.find() || keyword.equals(itemTypeEntity.getId().toString()));
                    }).collect(Collectors.toList());
        }
        if (CollectionUtil.isEmpty(itemTypeList)) {
            pageResult.setTotalCount(0);
            pageResult.setTotalPage(0);
            return pageResult;
        }
        pageResult.setTotalCount(itemTypeList.size());
        pageResult.calculateTotalPage();
        // 3.分页
        itemTypeList = itemTypeList.stream()
                .skip((pageNo - 1) * pageSize)
                .limit(pageSize)
                .collect(Collectors.toList());
        pageResult.setDataList(itemTypeList);
        return pageResult;
    }

    /**
     * 查询全部物品类型
     *
     * @return List<ItemTypeEntity>
     */
    @Override
    public List<ItemTypeEntity> findAll() {
        return redisCacheUtil.queryList(CACHE_ITEM_TYPE_LIST_KEY, ItemTypeEntity.class, "asc", this::getAll,
                CACHE_ITEM_TYPE_LIST_KEY_TTL, TimeUnit.SECONDS);
    }

    /**
     * 查询全部物品类型
     *
     * @return List<ItemTypeEntity>
     */
    private List<ItemTypeEntity> getAll(String sort) {
        return this.query()
                .orderBy(sort != null, "asc".equals(sort), "id")
                .list();
    }

    /**
     * 按id查询物品类型
     *
     * @param id 物品类型id
     * @return RoleEntity
     */
    @Override
    public ItemTypeEntity queryInfoById(Long id) {
        if (id == null || id <= 0) {
            MyException.throwException("查询失败: 物品类型id不能为null且必须大于0");
        }
        return this.getById(id);
    }

    /**
     * 新增物品类型
     *
     * @param itemTypeSaveVO 物品类型新增/修改请求体
     * @return Result
     */
    @Override
    public Result insertItemType(ItemTypeSaveVO itemTypeSaveVO) {
        ItemTypeEntity itemTypeEntity = BeanUtil.copyProperties(itemTypeSaveVO, ItemTypeEntity.class);
        if (!this.save(itemTypeEntity)) {
            MyException.throwException("物品类型信息失败");
        }
        // 删除redis缓存
        redisCacheUtil.deleteByKey(CACHE_ITEM_TYPE_LIST_KEY);
        return Result.ok("新增成功");
    }

    /**
     * 修改物品类型
     *
     * @param itemTypeSaveVO 物品类型新增/修改请求体
     * @return Result
     */
    @Transactional(rollbackFor = {Exception.class})
    @Override
    public Result updateItemType(ItemTypeSaveVO itemTypeSaveVO) {
        ItemTypeEntity itemTypeEntity = BeanUtil.copyProperties(itemTypeSaveVO, ItemTypeEntity.class);
        if (!this.updateById(itemTypeEntity)) {
            MyException.throwException("修改物品类型失败");
        }
        // 删除redis缓存
        redisCacheUtil.deleteByKey(CACHE_ITEM_TYPE_LIST_KEY);
        return Result.ok("修改成功");
    }

    /**
     * 批量删除物品类型
     *
     * @param itemTypeIds 物品类型ids
     * @return Result
     */
    @Transactional(rollbackFor = {Exception.class})
    @Override
    public Result deleteBatchItemType(List<Long> itemTypeIds) {
        if (CollectionUtil.isEmpty(itemTypeIds)) {
            MyException.throwException("删除失败: itemTypeIds为空");
        }
        this.removeByIds(itemTypeIds);
        // 删除redis缓存
        redisCacheUtil.deleteByKey(CACHE_ITEM_TYPE_LIST_KEY);
        return Result.ok("删除成功");
    }

}